﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Excel = Microsoft.Office.Interop.Excel;
using ObjectModel.Excel;
using MVVM.Core;
using System.Windows.Forms.Integration;
using ViewComponents;

namespace ViewModels
{
    public class ExcelViewModelManager
    {
        readonly Excel.Application mApp = Globals.Application;
        readonly Dictionary<Excel.Workbook, ViewModelBase> mViewModels = new Dictionary<Excel.Workbook, ViewModelBase>();
        readonly ElementHost mHostControl;

        public ExcelViewModelManager(out ElementHost hostControl)
        {
            mHostControl = new ElementHost();
            
            //add any workbooks already open to the dictionary
            foreach (Excel.Workbook wb in mApp.Workbooks)
                Add(wb);

            //assign active view model to property for binding
            ActiveViewModel = mViewModels[mApp.ActiveWorkbook];
            
            HookUpEvents();

        	hostControl = mHostControl;
        }

        public ViewModelBase ActiveViewModel
        {
            set
            {
                mHostControl.Child = value.View;
            }
        }

        void Add(Excel.Workbook wb)
        {
            if (!mViewModels.ContainsKey(wb))
            {
                ViewModelBase viewModel = new LinkedRangesViewModel() { View = new ParentContainerControl() };

                mViewModels.Add(wb, viewModel);
            }
        }

        void Remove(Excel.Workbook wb)
        {
            if (mViewModels.ContainsKey(wb))
                mViewModels.Remove(wb);
        }

        void App_AfterNewWorkbook(Excel.Workbook wb)
        {
            Add(wb);
            Refresh();
        }

        void App_WorkbookOpen(Excel.Workbook wb)
        {
            Add(wb);
            Refresh();
        }

        void App_WorkbookClose(Excel.Workbook wb, ref bool cancel)
        {
            if(!cancel) Remove(wb);
            Refresh();
        }

        /// <summary>
        /// Listen for new Workbook level events 
        /// </summary>
        void HookUpEvents()
        {
            ((Excel.AppEvents_Event)mApp).NewWorkbook += App_AfterNewWorkbook;
            mApp.WorkbookOpen += App_WorkbookOpen;
            ((Excel.AppEvents_Event)mApp).WorkbookBeforeClose += App_WorkbookClose;
            mApp.WindowActivate += App_WindowActivate;
        }

        void App_WindowActivate(Excel.Workbook wb, Excel.Window Wn)
        {
            ViewModelBase viewModel;
            if (mViewModels.TryGetValue(wb, out viewModel))
                ActiveViewModel = viewModel;
        }

        void Refresh()
        {
            ViewModelBase viewModel;
            if (mViewModels.TryGetValue(mApp.ActiveWorkbook, out viewModel))
                ActiveViewModel = viewModel;
        }
    }
}
